package com.javatip.project.deep_learning.app01Dataset.controller;

import java.io.BufferedReader;
import java.io.File;
import java.io.IOException;
import java.io.InputStreamReader;
import java.util.*;
import org.springframework.util.FileCopyUtils;
import com.javatip.common.utils.ImageResizer;
import com.javatip.project.deep_learning.model.domain.Model;
import com.javatip.project.system.user.domain.User;
import com.javatip.project.system.user.service.IUserService;
import com.javatip.project.system.user.service.UserServiceImpl;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpStatus;
import org.springframework.http.ResponseEntity;
import org.springframework.stereotype.Controller;
import org.springframework.ui.ModelMap;
import org.springframework.web.bind.annotation.*;
import com.javatip.project.deep_learning.app01Dataset.domain.App01Dataset;
import com.javatip.project.deep_learning.app01Dataset.service.IApp01DatasetService;
import com.javatip.framework.web.controller.BaseController;
import com.javatip.framework.web.page.TableDataInfo;
import com.javatip.framework.web.domain.AjaxResult;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.multipart.MultipartHttpServletRequest;
//import org.springframework.context.ApplicationContext;

/**
 * 数据集信息操作处理
 *
 * @author 袁伟
 * @date 2024-06-18
 */
@Api(tags = "语义分割数据集管理")
@Controller
@RequestMapping("/deep_learning/app01Dataset")
public class App01DatasetController extends BaseController {
    private String prefix = "deep_learning/app01Dataset";

    @Autowired
    private IApp01DatasetService app01DatasetService;
    @Autowired
    private UserServiceImpl userServiceImpl;
    @Autowired
    private IUserService userService;

//    @Autowired
//    private ApplicationContext applicationContext;

    @RequiresPermissions("deep_learning:app01Dataset:view")
    @GetMapping()
    public String app01Dataset() {
        return prefix + "/app01Dataset";
    }

    /**
     * 查询数据集列表
     */
    @ApiOperation(value = "查询所有数据集列表")
    @RequiresPermissions("deep_learning:app01Dataset:list")
    @PostMapping("/list")
    @ResponseBody
    public TableDataInfo list(App01Dataset app01Dataset) {
//        startPage();
        List<App01Dataset> list = app01DatasetService.selectApp01DatasetList(app01Dataset);
//        System.out.println(list);
        //        添加用户名
        for (App01Dataset m : list) {
            String userName = userService.getUsernameByUserId(Long.valueOf(m.getUserId()));
            m.setUserName(userName);
        }
        return getDataTable(list);
    }


    @RequiresPermissions("deep_learning:app01Dataset:list")
    @PostMapping("/getList")
    @ResponseBody
    public List<App01Dataset> getList(App01Dataset app01Dataset) {
//        startPage();
        List<App01Dataset> list = app01DatasetService.selectApp01DatasetList(app01Dataset);
//        System.out.println(list);
        //        添加用户名
        for (App01Dataset m : list) {
            String userName = userService.getUsernameByUserId(Long.valueOf(m.getUserId()));
            m.setUserName(userName);
        }
        return list;
    }


    //    返回公开或者自己的数据集列表
    @RequiresPermissions("deep_learning:app01Dataset:list")  //不能乱改，否则会报错
    @PostMapping("/listWithParas")
    @ResponseBody
    public TableDataInfo listWithParas(App01Dataset app01Dataset) {
//        startPage();
        System.out.println("listWithParas");
        List<App01Dataset> list = app01DatasetService.selectApp01DatasetList(app01Dataset);
//        TableDataInfo dataTable = getDataTable(list);
//        筛选list中的数据，只返回当前用户和isPublic为1的数据集
        List<App01Dataset> list1 = new ArrayList<>();
        User currentUser = getSysUser();
        int currentUserId = Integer.parseInt(String.valueOf(currentUser.getUserId()));
//        System.out.println("当前用户id: " + currentUserId);
        for (App01Dataset dataset : list) {
//            System.out.println("dataset.getUserId() = " + dataset);
            if (dataset.getIsPublic() != null) {
                if (dataset.getUserId() == currentUserId || dataset.getIsPublic() == 1) {
                    list1.add(dataset);
                }
            }
        }
//        System.out.println(list1);
        //        添加用户名
        for (App01Dataset m : list1) {
            String userName = userService.getUsernameByUserId(Long.valueOf(m.getUserId()));
            m.setUserName(userName);
        }
        return getDataTable(list1);
//        return dataTable;
    }

    //    返回公开或者自己的数据集列表 (Get请求)
    @RequiresPermissions("deep_learning:app01Dataset:list")  //不能乱改，否则会报错
    @PostMapping("/listWithParasGet")
    @ResponseBody
    public TableDataInfo listWithParasGet(App01Dataset app01Dataset) {
//        startPage();
        System.out.println("listWithParasGet");
        List<App01Dataset> list = app01DatasetService.selectApp01DatasetList(app01Dataset);
//        TableDataInfo dataTable = getDataTable(list);
//        筛选list中的数据，只返回当前用户和isPublic为1的数据集
        List<App01Dataset> list1 = new ArrayList<>();
        User currentUser = getSysUser();
        int currentUserId = Integer.parseInt(String.valueOf(currentUser.getUserId()));
//        System.out.println("当前用户id: " + currentUserId);
        for (App01Dataset dataset : list) {
//            System.out.println("dataset.getUserId() = " + dataset);
            if (dataset.getIsPublic() != null) {
                if (dataset.getUserId() == currentUserId || dataset.getIsPublic() == 1) {
                    list1.add(dataset);
                }
            }
        }
        //        添加用户名
        for (App01Dataset m : list1) {
            String userName = userService.getUsernameByUserId(Long.valueOf(m.getUserId()));
            m.setUserName(userName);
        }
        return getDataTable(list1);
//        return dataTable;
    }

    //	处理delete删除请求，删除数据集对应文件夹
//    @PostMapping("/delete/{id}")
//    @ResponseBody
//    public ResponseEntity<String> delete(@PathVariable("id") Integer id) {
//        System.out.println("delete-Controller地址：" + app01DatasetService.selectApp01DatasetById(id).getLocation());
//        int result = app01DatasetService.deleteApp01DatasetWithDB(String.valueOf(id), app01DatasetService.selectApp01DatasetById(id).getLocation());
//        if (result == 1) {
//            return ResponseEntity.ok("删除成功" + id);
//        } else {
//            return ResponseEntity.status(HttpStatus.BAD_REQUEST).body("删除失败 " + id);
//        }
//    }

    //    只返回自己的数据集列表
    @RequiresPermissions("deep_learning:app01Dataset:list")  //不能乱改，否则会报错
    @PostMapping("/listWithOnlyUserId")
    @ResponseBody
    public TableDataInfo listWithOnlyUserId(App01Dataset app01Dataset) {
//        startPage();
        System.out.println("listWithOnlyUserId");
        List<App01Dataset> list = app01DatasetService.selectApp01DatasetList(app01Dataset);
//        TableDataInfo dataTable = getDataTable(list);
//        筛选list中的数据，只返回当前用户和isPublic为1的数据集
        List<App01Dataset> list1 = new ArrayList<>();
        User currentUser = getSysUser();
        int currentUserId = Integer.parseInt(String.valueOf(currentUser.getUserId()));
//        System.out.println("当前用户id: " + currentUserId);
        for (App01Dataset dataset : list) {
//            System.out.println("dataset.getUserId() = " + dataset);
            if (dataset.getIsPublic() != null) {
                if (dataset.getUserId() == currentUserId
//                        || dataset.getIsPublic() == 1
                ) {
                    list1.add(dataset);
                }
            }
        }
//        System.out.println(list1);
        //        添加用户名
        for (App01Dataset m : list1) {
            String userName = userService.getUsernameByUserId(Long.valueOf(m.getUserId()));
            m.setUserName(userName);
        }
        return getDataTable(list1);
//        return dataTable;
    }

    /**
     * 新增数据集
     */
    @GetMapping("/add")
    public String add() {
        return prefix + "/add";
    }

    /**
     * 新增保存数据集
     */
    @RequiresPermissions("deep_learning:app01Dataset:add")
    @PostMapping("/add")
    @ResponseBody
    public AjaxResult addSave(App01Dataset app01Dataset) {
        return toAjax(app01DatasetService.insertApp01Dataset(app01Dataset));
    }

    /**
     * 修改数据集
     */
    @GetMapping("/edit/{id}")
    public String edit(@PathVariable("id") Integer id, ModelMap mmap) {
        App01Dataset app01Dataset = app01DatasetService.selectApp01DatasetById(id);
        mmap.put("app01Dataset", app01Dataset);
        return prefix + "/edit";
    }

    /**
     * 修改保存数据集
     */
    @RequiresPermissions("deep_learning:app01Dataset:edit")
    @PostMapping("/edit")
    @ResponseBody
    public AjaxResult editSave(App01Dataset app01Dataset) {
        return toAjax(app01DatasetService.updateApp01Dataset(app01Dataset));
    }

    /**
     * 删除数据集
     */
    @RequiresPermissions("deep_learning:app01Dataset:remove")
    @PostMapping("/remove")
    @ResponseBody
    public AjaxResult remove(String ids) {
        return (app01DatasetService.deleteApp01DatasetByIds(ids));
    }

    /**
     * 删除数据集
     */
//    @RequiresPermissions("deep_learning:app01Dataset:remove")
//    @PostMapping("/remove")
//    @ResponseBody
//    public AjaxResult remove(String ids, String location) {
//        System.out.println(location);
//        return toAjax(app01DatasetService.deleteApp01DatasetWithDB(ids, location));
//    }

    //    上传数据集
    @ResponseBody
    @PostMapping("/uploadDataset")
    public String handleUploadRequest(MultipartHttpServletRequest request) {
        List<MultipartFile> image = request.getFiles("image-upload");
        List<MultipartFile> label = request.getFiles("label-upload");
//
//        List<MultipartFile> imageVal = request.getFiles("imageVal-upload");
//        List<MultipartFile> labelVal = request.getFiles("labelVal-upload");

        System.out.println("uploadDataset-Controller");
//        System.out.println("image.size() = " + image.size());
//        System.out.println("imageVal.size() = " + imageVal.size());
//        System.out.println("图片高度:" + request.getParameter("height"));

        // 获取数据集名称
        String datasetName = request.getParameter("datasetName");
        User currentUser = getSysUser();
        int currentUserId = Integer.parseInt(String.valueOf(currentUser.getUserId()));
        String currentPath = System.getProperty("user.dir").replace("\\","/");
        String destinationPath = currentPath + "/src/main/resources/datasets/" + String.valueOf(currentUserId); // 指定保存文件的目标路径
//        System.out.println("当前路径: " + currentPath);
        App01Dataset dataset = app01DatasetService.selectApp01DatasetByNameAndUserId(datasetName, currentUserId);
//        获取是否公开
        int isPublic = Integer.parseInt(request.getParameter("isPublic"));
        boolean isJson = false;
        boolean isTif = false;

        //处理上传文件
        if (image != null && !image.isEmpty()
                && datasetName != null && !datasetName.isEmpty()) {
            try {
                File destinationDir = new File(destinationPath, datasetName); // 创建文件夹路径
                if (!destinationDir.exists()) {
                    destinationDir.mkdirs(); // 创建文件夹
                }


                File trainImageDir = new File(destinationDir, "image"); // 创建image文件夹路径
                if (!trainImageDir.exists()) {
                    trainImageDir.mkdirs(); // 创建image文件夹
                }

                File trainLabelDir = new File(destinationDir, "label"); // 创建label文件夹路径
                if (!trainLabelDir.exists()) {
                    trainLabelDir.mkdirs(); // 创建label文件夹
                }

                File trainLabel1Dir = new File(destinationDir, "label1"); // 创建label1文件夹路径
                if (!trainLabel1Dir.exists()) {
                    trainLabel1Dir.mkdirs(); // 创建label文件夹
                }


////                判断image文件是否是tif格式
//                for (MultipartFile file : image) {
//                    if (file.getOriginalFilename().endsWith(".tif")) {
//                        isTif = true;
//                        break;
//                    }
//                }

//                System.out.println("label:"+label);
//                System.out.println("label.isEmpty():"+label.isEmpty());
////                  判断label文件是否是json格式
//                for (MultipartFile file : label) {
//                    // 如果label文件是json格式或者label为空
//                    if (file.getOriginalFilename().endsWith(".json") ) {
//                        isJson = true;
//                        break;
//                    }
//                }
//                if (label.isEmpty() && isTif){
//                    isJson = true;
//                }

////                如果iamge文件是tif格式，则创建json文件夹
//                System.out.println("isTif: " + isTif);
//                System.out.println("isJson: " + isJson);
//                File trainJsonDir = new File(destinationDir, "json"); // 创建json文件夹路径
//                if (isTif && isJson) {
//                    if (!trainJsonDir.exists()) {
//                        trainJsonDir.mkdirs(); // 创建label文件夹
//                    }
//                }
//                else {
//                    if (isTif || isJson) {
//                        return "图片和标签文件格式不匹配";
//                    }
//                }

                // 检查 image 集合
                for (MultipartFile file : image) {
                    // 复制文件到 image 文件夹
                    File destinationFile1 = new File(trainImageDir, file.getOriginalFilename());
                    file.transferTo(destinationFile1); // 首次传输

                    // 如果文件是 .tif 格式，复制到 tif 文件夹
                    if (file.getOriginalFilename().endsWith(".tif")) {
                        File trainTifDir = new File(destinationDir, "tif");
                        if (!trainTifDir.exists()) {
                            trainTifDir.mkdirs();
                        }
                        File destinationFile2 = new File(trainTifDir, file.getOriginalFilename());
                        // 使用 FileCopyUtils 复制到 tif 文件夹
                        FileCopyUtils.copy(destinationFile1, destinationFile2);
                    }
                }


                boolean isTifImage=false;
                for (MultipartFile file : label) {
//                    // 保存文件到指定位置
                    File destinationFile1 = new File(trainLabelDir, file.getOriginalFilename());
//                  如果label不是json格式
//                    if (!file.getOriginalFilename().endsWith(".json")) {
                        System.out.println("trainLabelDir: "+trainLabelDir);
                        file.transferTo(destinationFile1); // 复制文件到label文件夹}
//                        // 如果文件是 .tif 格式，复制到 tif 文件夹
//                        if (file.getOriginalFilename().endsWith(".tif")) {
//                            File trainTifDir = new File(destinationDir, "tifLabel");
//                            if (!trainTifDir.exists()) {
//                                trainTifDir.mkdirs();
//                            }
//                            File destinationFile2 = new File(trainTifDir, file.getOriginalFilename());
//                            // 使用 FileCopyUtils 复制到 tif 文件夹
//                            FileCopyUtils.copy(destinationFile1, destinationFile2);
//                        }
                        //复制一份到label1
                        File destinationFile2 = new File(trainLabel1Dir, file.getOriginalFilename());
                        // 使用 FileCopyUtils 复制到 tif 文件夹
                        FileCopyUtils.copy(destinationFile1, destinationFile2);

//                    }
//                    如果label是json格式
//                    else {
//                        file.transferTo(new File(trainJsonDir, file.getOriginalFilename())); // 复制文件到json文件夹
//                        isTifImage=true;
//                    }
                }
//                if (isTifImage){
//                    // 调用Python脚本处理JSON文件
//                    ProcessBuilder processBuilder = new ProcessBuilder(
//                            "python3",
//                            "src/main/resources/CorsicanFire/utils/processGeo.py",  // 替换为Python脚本的实际路径
//                            trainJsonDir.toString(),   // vector_dir 路径
//                            trainImageDir.toString(),   // ref_img_dir 路径
//                            trainLabelDir.toString()    // output_dir 路径
//                    );
//                    // 启动进程
//                    processBuilder.redirectErrorStream(true);
//                    Process process = processBuilder.start();
//                    // 读取Python脚本输出（可选）
//                    BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream()));
//                    String line;
//                    while ((line = reader.readLine()) != null) {
//                        System.out.println(line);
//                    }
//
//                    // 等待Python脚本执行完毕
//                    int exitCode = process.waitFor();
//                    System.out.println("Python script finished with exit code: " + exitCode);
//                }


                //写入数据库
                if (dataset == null) {
                    // 如果名称不存在，则创建新记录
                    dataset = new App01Dataset();
                    dataset.setName(datasetName);
                    dataset.setNumTrain(image.size());
                    dataset.setNumVall(label.size());
                    dataset.setUserId(currentUserId);
                    //上传时间设置为当前时间
                    dataset.setUploadTime(new Date());
                    dataset.setLocation(destinationPath + "/" + datasetName + "/"); // 设置路径
                    dataset.setHeight(Integer.parseInt(request.getParameter("height")));
                    dataset.setWidth(Integer.parseInt(request.getParameter("width")));
                    //默认不公开
                    dataset.setIsPublic(0);
//                    获取是否公开
                    if (isPublic == 1) {
                        dataset.setIsPublic(1);
                    } else {
                        dataset.setIsPublic(0);
                    }
//            System.out.println("destinationPath + \"/\" + datasetName" + destinationPath + "/" + datasetName + "/");
                    // 保存到数据库
                    app01DatasetService.insertApp01Dataset(dataset);
                } else {
                    System.out.println("更新数据集信息");
//                    dataset.setName(datasetName);
                    dataset.setNumTrain(image.size());
                    dataset.setNumVall(label.size());
//                    dataset.setUserId(currentUserId);
                    //上传时间设置为当前时间
                    dataset.setUploadTime(new Date());
                    dataset.setLocation(destinationPath + "/" + datasetName + "/"); // 设置路径
                    dataset.setHeight(Integer.parseInt(request.getParameter("height")));
                    dataset.setWidth(Integer.parseInt(request.getParameter("width")));
                    app01DatasetService.updateApp01Dataset(dataset);
                }


//                ImageResizer.resizeAndConvertImages(destinationPath,Integer.parseInt(request.getParameter("height")),Integer.parseInt(request.getParameter("width")));
                // 启动新线程执行异步任务
                new Thread(() -> {
                    try {
                        System.out.println("destinationPath:" + destinationPath);
                        // 耗时操作，譬如 ImageResizer
                        ImageResizer.resizeAndConvertImages(destinationPath + "/" + datasetName + "/",
                                Integer.parseInt(request.getParameter("height")),
                                Integer.parseInt(request.getParameter("width")));
                    } catch (Exception e) {
                        e.printStackTrace();
                    }
                }).start();
//                applicationContext.getClassLoader().clearAssertionStatus();
                return "文件上传成功";
            } catch (IOException e) {
                e.printStackTrace();
                return "文件上传失败";
            }
//            catch (InterruptedException e) {
//                throw new RuntimeException(e);
//            }
        } else {
            return "未选择文件或文件夹名为空";
        }
    }


    // 查看数据集
    @GetMapping("/dataset/api/files")
    @ResponseBody
    public List<Map<String, String>> getFiles(@RequestParam String path) {
        System.out.println("Received path: " + path);

        String location = path.substring(path.lastIndexOf("datasets"));
        System.out.println("location" + location);

        File imageDir = new File(path, "image");
        File labelDir = new File(path, "label");
        System.out.println("imageDir: " + imageDir);
        System.out.println("labelDir: " + labelDir);

        List<Map<String, String>> filePairs = new ArrayList<>();

        if (imageDir.exists() && imageDir.isDirectory()) {
            File[] imageFiles = imageDir.listFiles();
            File[] labelFiles = labelDir.exists() && labelDir.isDirectory() ? labelDir.listFiles() : new File[0];

            if (imageFiles != null) {
                for (File imageFile : imageFiles) {
                    String imageName = imageFile.getName();
                    String imageBaseName = imageName.substring(0, imageName.lastIndexOf('.'));

                    boolean labelFound = false;

                    for (File labelFile : labelFiles) {
                        String labelName = labelFile.getName();
                        String labelBaseName = labelName.substring(0, labelName.lastIndexOf('.'));

                        if (imageBaseName.equals(labelBaseName)) {
                            Map<String, String> filePair = new HashMap<>();
                            filePair.put("image", "/" + location + "/image/" + imageName);
                            filePair.put("label", "/" + location + "/label/" + labelName);
                            int[] imageWidthAndHeight = ImageResizer.getImageWidthAndHeight(imageFile);
                            filePair.put("size", imageWidthAndHeight[0] + "x" + imageWidthAndHeight[1]);
                            filePairs.add(filePair);
                            labelFound = true;
                            break;
                        }
                    }

                    if (!labelFound) {
                        Map<String, String> filePair = new HashMap<>();
                        filePair.put("image", "/" + location + "/image/" + imageName);
                        filePair.put("label", "/" + location + "/image/" + imageName); // 使用相同的路径作为占位符
                        int[] imageWidthAndHeight = ImageResizer.getImageWidthAndHeight(imageFile);
                        filePair.put("size", imageWidthAndHeight[0] + "x" + imageWidthAndHeight[1]);
                        filePairs.add(filePair);
                    }
                }
            }
        }
        return filePairs;
    }


    /**
     * 获取当前登录用户的id
     *
     * @return
     */
    @ResponseBody
    @GetMapping("/currentUser")
    public Map<String, Object> getCurrentUserAlt() {
        Map<String, Object> response = new HashMap<>();

        int userId = getSysUser().getUserId().intValue();
        boolean admin = getSysUser().isAdmin();
        System.out.println("admin："+admin);
        if (admin){
            System.out.println("当前用户是管理员");
            response.put("userId",1);
            response.put("status", "success");
            return response;
        }
        // 假设 authentication.getName() 返回的就是 userId
        response.put("userId", userId); // 返回用户名作为 userId
        response.put("status", "success");
        return response;
    }


    @ResponseBody
    @PostMapping("/resizePicture")
    public void resizePicture(int id, int height, int width) {
        App01Dataset app01Dataset = app01DatasetService.selectApp01DatasetById(id);
        String location = app01Dataset.getLocation();
        System.out.println("location: " + location);
        System.out.println("height: " + height);
        System.out.println("width: " + width);
        ImageResizer.resizeAndConvertImages(location, height, width);
    }

    /**
     * 检查数据集名称是否存在
     *
     * @param name
     * @return
     */
    @GetMapping("/checkDatasetNameUnique")
    @ResponseBody
    public ResponseEntity<Boolean> checkDatasetNameUnique(@RequestParam("name") String name) {
        System.out.println("检测数据集名称是否存在");
        int userId = getSysUser().getUserId().intValue();
        boolean exists = app01DatasetService.isPredictNameExists(name, userId); // 该方法检查任务名称是否存在
        return ResponseEntity.ok(exists);

//        不检查名字了
//        return ResponseEntity.ok(false);
    }

}
